/*******************************************
 * Copyright 2007 Aphrodite Framework for javaME .
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the GNU Public License v2.0
 * which accompanies this distribution, and is available at
 * http://www.gnu.org/licenses/old-licenses/gpl-2.0.html
 * Email : owner@aphroditeme.dev.java.net
 * Contributors:
 *     Kent Elton - initial API and implementation
 *******************************************/

package com.aphrodite.ui.widgets;

import javax.microedition.lcdui.Graphics;

import com.aphrodite.ui.schema.TableCell;
import com.aphrodite.util.BitmapFont;
import com.aphrodite.util.StringUtil;

/*
 * fix logic in calcRowscanAccomodate
 * focus handling 
 * state change notification
 * implement traverse
 */

/**
 * <p>
 * Table Item
 * </p>
 * Uses a bitmap font for text based rendering<br/> Max no of rows 32000. Max no
 * of cols 32000
 */
public final class BitmapFontTable extends TabularItem {

	private BitmapFont currentFont;
	private final BitmapFont font;

	/**
	 * Create a with bitmap font
	 * 
	 * @param theme
	 *            Theme to use
	 * @param cells
	 *            table cell info
	 * @param columnWidth
	 *            width of each column in the table, if null the default column
	 *            width is used
	 * @param font
	 *            bitmap font to be used in table drawing
	 * @param width
	 * @param height
	 */
	public BitmapFontTable(Theme theme, TableCell[][] cells, short[] columnWidth, BitmapFont font, int width, int height) {
		super(theme, cells, columnWidth, width, height);
		this.font = font;
	}

	// private int calulateEndRowOnInit() {
	// int rows = (totalRows >= 10) ? 10 : totalRows - 1;
	// int totalHeight = 0;
	// totalHeight += (rowFreeze) ? rowHt[frozenRow] : rowHt[0];
	// for (int i = 1; i < rowHt.length; i++) {
	// totalHeight += rowHt[i];
	// if (totalHeight > height) {
	// rows = i - 1;
	// }
	// }
	// return rows;
	// }

	/**
	 * calculate row height
	 */
	protected final void calcRowHeight() {
		rowHeight = new short[totalRows];
		// TODO remove padding
		int longestCell;
		for (int i = 0; i < totalRows - paddingRows; i++) {
			longestCell = getLongestCellIndex(tableData[i]);
			/*
			 * if the longest cell has a col-span then we dont need to calc the
			 * height
			 */
			int t = (tableData[i][longestCell]).columnSpan == 1 ? getRowHt(tableData[i][longestCell], longestCell)
					: font.getFont(tableData[i][longestCell].fontStyle).getHeight() + (lineSpacing * 2);
			rowHeight[i] = (short) t;
		}
		/* set the row height for the padding rows */
		for (int i = totalRows - paddingRows; i < totalRows; i++) {
			rowHeight[i] = 80;
		}
	}

	private final void drawFittingText(final Graphics g, final TableCell cell, int fontHeight, final int textWidth,
			final int row, final int column) {
		/* calc the V-Center for the cell */
		int vCenter = (tempRowHt[row] / 2) - (fontHeight / 2);
		currentFont.drawString(g, cell.cellCaption, getTextIndent(column, cell, textWidth), cellYpos + vCenter, 0);
	}

	/**
	 * get the current font to be used
	 * 
	 * @param style
	 * @return
	 */
	private BitmapFont getCurrFont(final byte style) {
		switch (style) {
		case 0:
			currentFont = font;
		default:
			currentFont = font.getFont(style);
			break;
		}
		return (currentFont == null) ? font : currentFont;
	}

	protected final int getRowHt(TableCell cell, int column) {
		BitmapFont tmpFont = font.getFont(cell.fontStyle);
		String[] lines = getWrapLines(cell.cellCaption, tmpFont, colWdth[column]
				- ((cell.textIndent == 1) ? textLeftPad : textRtPad));
		return (lineSpacing * 2) + ((tmpFont.getHeight() + lineSpacing) * lines.length - 1);

	}

	private final String[] getWrapLines(final String text, final BitmapFont font, final int cellWidth) {
		return StringUtil.doTextWrap(text, font, cellWidth, cellWidth);
	}

	// int scrollEnd;
	public final void render(final Graphics g) {
		if (!isVisible)
			return;

		capture(g, width, height, false);
		drawCols(g);
		int row, column, fontHeight, textWidth;
		String[] lines;
		for (row = 0; row < rowsCanAcc + 1; row++) {
			g.setColor(theme.borderColor);
			cellYpos = getCellYPosition(row);
			g.drawLine(0, cellYpos, width - 1, cellYpos);
			for (column = 0; column < colsCanAcc; column++) {
				/*
				 * skip drawing of column span is 0 for this cell / or if the
				 * row height is 0 (frozen row)
				 */
				if (tempTblData[row][column] != null && tempRowHt[row] > 0) {
					if (tempTblData[row][column].columnSpan > 0) {
						cellXpos = getCellXPosition(column);
						/* get the current cell font */
						currentFont = getCurrFont(tempTblData[row][column].fontStyle);
						fontHeight = currentFont.getHeight();
						textWidth = currentFont.stringWidth(tempTblData[row][column].cellCaption);
						// fill the cell color
						paintCellColor(g, row, column);
						g.setColor(tempTblData[row][column].fontColor);
						/*
						 * if the text fits the cell or needs to be column
						 * spanned
						 */
						if (textWidth <= tempColWdth[column]
								- ((tempTblData[row][column].textIndent == 1) ? textLeftPad : textRtPad)
								|| tempTblData[row][column].columnSpan > 1) {
							drawFittingText(g, tempTblData[row][column], fontHeight, textWidth, row, column);
						} else {/* wrap the text to fit in the cell */
							fontHeight = fontHeight + lineSpacing;
							lines = getWrapLines(tempTblData[row][column].cellCaption, currentFont, tempColWdth[column]
									- ((tempTblData[row][column].textIndent == 1) ? textLeftPad : textRtPad));
							for (int i = 0; i < lines.length; i++) {
								currentFont.drawString(g, lines[i], getTextIndent(column, tempTblData[row][column],
										currentFont.stringWidth(lines[i])), (cellYpos) + 2 + fontHeight * i, 0);
							}
						}
					}
				}
			}
		}
		/* Draw the selector rectangle */
		g.setColor(theme.highLightColor);
		g.drawRect(getCellXPosition(selectedCol), getCellYPosition(selectedRow), tempColWdth[selectedCol],
				tempRowHt[selectedRow]);

		/* fill the remaning empty space if any */
		// if (cellYpos < width) {
		// g.setColor(bgColor);
		// g.fillRect(x, y + cellYpos + tempRowHeight[row - 1], x + width,
		// height
		// - (cellYpos + scrollBarH.getHeight()));
		// }
		// draw the zoom rectangle
		if (doCellZoom) {
			doCellZoom(g);
		}
		// draw the scrollbars
		sBarV.render(g);
		sBarH.render(g);
		release(g, width, height, true);

	}

	protected final void updateModel() {}

}
